package com.klun.concDesign.chapterFive.Disruptor_5_4;

import com.lmax.disruptor.BlockingWaitStrategy;
import com.lmax.disruptor.RingBuffer;
import com.lmax.disruptor.dsl.Disruptor;
import com.lmax.disruptor.dsl.ProducerType;

import java.nio.ByteBuffer;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;

public class Producer {
    private final RingBuffer<PCdata> ringBuffer;

    public Producer(RingBuffer<PCdata> ringBuffer) {
        this.ringBuffer = ringBuffer;
    }
    // ByteBuffer java.nio 中的类！！ ByteBuffer:使用这个是因为这个可以储存任何数据类型
    public void pushData(ByteBuffer bb){
        long sequeue = ringBuffer.next();
        try{
            PCdata pCdata = ringBuffer.get(sequeue);
            // 取零 ！！ 索引起始位
            pCdata.setValue(bb.getLong(0));
        } finally {
            ringBuffer.publish(sequeue);
        }
    }

    /**
     * 调用 方式
     * @param args
     * @throws InterruptedException
     */
    public static void main(String[] args) throws InterruptedException {
        
        ExecutorService executorService = Executors.newFixedThreadPool(5);


        PCdataFactory factory = new PCdataFactory(); //作用？
        int bufferSize = 1024; //
        // BlockingWaitStrategy:更新通知策略
        Disruptor<PCdata> pCdataDisruptor
                = new Disruptor<>(factory, bufferSize, executorService, ProducerType.MULTI, new BlockingWaitStrategy());

        // 设置了4个消费者线程
        pCdataDisruptor.handleEventsWithWorkerPool(
                new Consumer(),
                new Consumer(),
                new Consumer(),
                new Consumer()
        );
        // 启动 disruptor
        pCdataDisruptor.start();

        RingBuffer<PCdata> ringBuffer = pCdataDisruptor.getRingBuffer();
        Producer producer = new Producer(ringBuffer);
        ByteBuffer allocate = ByteBuffer.allocate(10); // 创建一个8位的 ByteBuffer
        for(long l = 0;true;l++){
            //
            allocate.putLong(0, l);
            producer.pushData(allocate);
            Thread.sleep(100);
            System.out.println("add data: "+l);
            System.out.println();
        }


    }
}
